package com.biwei.app.wrap.service;

import com.biwei.app.wrap.bean.Currency;
import com.biwei.app.wrap.bean.CurrencyResult;
import com.biwei.app.wrap.remote.PublicService;
import com.biwei.app.wrap.remote.UserRemoteService;
import com.biwei.app.wrap.vo.Assets;
import com.biwei.app.wrap.vo.Token;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

@Service
public class UserService {

    private PublicService publicService;
    private UserRemoteService userRemoteService;
    private ObjectMapper objectMapper;

    public UserService(PublicService publicService, UserRemoteService userRemoteService, ObjectMapper objectMapper) {
        this.publicService = publicService;
        this.userRemoteService = userRemoteService;
        this.objectMapper = objectMapper;
    }

    /**
     * 查看资产列表
     * @return
     */
    public Assets assets() throws IOException {
        /**
         * 1、获取币基本信息
         2、获取当前用户的资产列表
         3、使用币基本信息补全列表
         4、获取币相对比特币的价格
         5、继续补全资产列表并增加总资产字段
         */
        Assets assets = new Assets();
        //1.获取币基本信息
        Map<String, Currency> currencyMap = new HashMap<>();
        Map<String, Token> tokenMap = new HashMap<>();
        String json = publicService.currencyResult();
        CurrencyResult currencyResult = objectMapper.readValue(json, CurrencyResult.class) ;
        if (currencyResult.getErrorCode() == 0) {
            currencyResult.getDataMap().getCurrencys().stream().forEach(c -> {
                currencyMap.put(c.getName(), c);
                Token token = new Token();
                token.setBtc(BigDecimal.ZERO);
                token.setBalance(BigDecimal.ZERO);
                token.setFrozen(BigDecimal.ZERO);
                token.setTrade(BigDecimal.ZERO);
                token.setName(c.getDescription());
                token.setSymbol(c.getName());
                tokenMap.put(c.getName(), token);
            });
            //2.获取当前用户的资产列表
            userRemoteService.accounts().getAccounts().stream().forEach(c -> {
                Token token = tokenMap.get(c.getCurrency());
                if (token == null) {
                    token = new Token();
                    tokenMap.put(c.getCurrency(), token);
                }
                if ("SPOT_AVAILABLE".equals(c.getType())) {
                    token.setTrade(c.getBalance());
                } else {
                    token.setFrozen(c.getBalance());
                }
                token.setSymbol(c.getCurrency());
                //3、使用币基本信息补全列表
                Currency currency = currencyMap.get(c.getCurrency());
                if (currency != null) {
                    token.setName(currency.getDescription());
                }
            });
            //4、获取币对交易价格并计算资产
            Map<String, BigDecimal[]> pricesMap =  publicService.marketPrices();
            BigDecimal[] ethBaseBtc = pricesMap.get("ETH_BTC");
            BigDecimal[] usdtBaseBtc = pricesMap.get("BTC_USDT");
            tokenMap.values().stream().forEach(token -> {
                token.setBalance(token.getFrozen().add(token.getTrade()));
                if ("BTC".equals(token.getSymbol())) {
                    token.setBtc(token.getBalance());
                } else if ("USDT".equals(token.getSymbol())) {
                    token.setBtc(token.getBalance().divide(usdtBaseBtc[4], 10, BigDecimal.ROUND_FLOOR));
                } else {
                    BigDecimal[] array = pricesMap.get(token.getSymbol() + "_BTC");
                    boolean onlyEth = false;
                    boolean onlyUsdt = false;
                    if (array == null) {
                        array = pricesMap.get(token.getSymbol() + "_ETH");
                        onlyEth = true;
                    }
                    if (array == null) {
                        array = pricesMap.get(token.getSymbol() + "_USDT");
                        onlyUsdt = true;
                    }
                    if (array != null) {
                        token.setBtc(token.getBalance().multiply(array[4]));
                    }
                    if (onlyEth) {
                        token.setBtc(token.getBtc().multiply(ethBaseBtc[4]));
                    } else if (onlyUsdt) {
                        token.setBtc(token.getBtc().divide(usdtBaseBtc[4], 10, BigDecimal.ROUND_FLOOR));
                    }
                }
                //5、继续补全资产列表并增加总资产字段
                assets.setTotal(assets.getTotal().add(token.getBtc()));
            });
            assets.setCurrencies(new ArrayList<>(tokenMap.values()));
        }
        return assets;
    }
}
